<!DOCTYPE html>
<html lang="zh-CN">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>炫酷科技贪吃蛇</title>
  <style>
    @import url('https://fonts.googleapis.com/css2?family=Orbitron:wght@700&display=swap');
    body {
      margin: 0;
      padding: 0;
      background: #0f2027;
      background: linear-gradient(135deg, #0f2027, #2c5364 80%);
      min-height: 100vh;
      font-family: 'Orbitron', 'Consolas', monospace;
      color: #fff;
      overflow: hidden;
    }
    .container {
      display: flex;
      flex-direction: column;
      align-items: center;
      justify-content: center;
      min-height: 100vh;
      z-index: 1;
    }
    h1 {
      font-size: 2.8rem;
      letter-spacing: 0.22em;
      color: #00ffe7;
      text-shadow: 0 0 24px #00ffe7, 0 0 48px #0ff;
      margin-bottom: 18px;
    }
    .scoreboard {
      display: flex;
      gap: 3em;
      margin-bottom: 1.2em;
      font-size: 1.35em;
      text-shadow: 0 0 10px #0ff;
      background: rgba(0,32,64,0.5);
      border-radius: 12px;
      padding: 0.3em 1.5em;
      border: 1.5px solid #00ffe7;
      box-shadow: 0 0 10px #00ffe744;
    }
    .controls {
      display: flex;
      align-items: center;
      gap: 1.5em;
      margin-bottom: 1.2em;
      background: rgba(0,32,64,0.5);
      border-radius: 12px;
      padding: 0.5em 1.5em;
      border: 1.5px solid #00ffe7;
      box-shadow: 0 0 10px #00ffe744;
    }
    .slider {
      width: 160px;
      height: 6px;
      accent-color: #00ffe7;
      background: #222;
      border-radius: 6px;
      outline: none;
      box-shadow: 0 0 8px #00ffe7;
    }
    .label {
      color: #00ffe7;
      font-weight: bold;
      text-shadow: 0 0 8px #0ff;
      font-size: 1.1em;
    }
    .btn {
      background: linear-gradient(90deg, #00ffe7 0%, #007cf0 100%);
      border: none;
      border-radius: 12px;
      color: #fff;
      font-size: 1.25em;
      font-weight: bold;
      padding: 0.7em 2.2em;
      cursor: pointer;
      box-shadow: 0 0 18px #00ffe7, 0 0 6px #007cf0;
      transition: transform 0.12s, box-shadow 0.18s;
      font-family: 'Orbitron', monospace;
      letter-spacing: 0.08em;
      margin-left: 0.5em;
    }
    .btn:hover {
      transform: scale(1.10);
      box-shadow: 0 0 36px #00ffe7, 0 0 12px #007cf0;
      filter: brightness(1.15);
    }
    #game-canvas {
      background: rgba(10, 20, 40, 0.98);
      border: 3px solid #00ffe7;
      border-radius: 22px;
      box-shadow: 0 0 48px #00ffe7, 0 0 12px #007cf0;
      margin-bottom: 1.2em;
      display: block;
      image-rendering: pixelated;
    }
    .game-over {
      position: absolute;
      top: 50%;
      left: 50%;
      transform: translate(-50%, -50%);
      background: rgba(0,0,0,0.92);
      border: 2.5px solid #00ffe7;
      border-radius: 20px;
      padding: 2.5em 3.5em 2em 3.5em;
      text-align: center;
      box-shadow: 0 0 40px #00ffe7;
      z-index: 10;
      color: #fff;
      font-size: 1.7em;
      text-shadow: 0 0 16px #00ffe7;
      display: none;
    }
    .game-over .btn {
      margin-top: 1.2em;
      font-size: 1.2em;
      padding: 0.6em 2em;
    }
    /* 动态粒子背景 */
    #bg-canvas {
      position: fixed;
      top: 0; left: 0; right: 0; bottom: 0;
      width: 100vw;
      height: 100vh;
      z-index: 0;
      pointer-events: none;
    }
  </style>
</head>
<body>
<canvas id="bg-canvas"></canvas>
<div class="container">
  <h1>炫酷贪吃蛇</h1>
  <div class="scoreboard">
    <div>分数：<span id="score">0</span></div>
    <div>最高分：<span id="highscore">0</span></div>
  </div>
  <div class="controls">
    <span class="label">速度</span>
    <input type="range" min="5" max="20" value="10" id="speed-slider" class="slider">
    <span id="speed-label" class="label">中速</span>
    <button class="btn" id="restart-btn">重新开始</button>
  </div>
  <canvas id="game-canvas" width="480" height="480"></canvas>
  <div class="game-over" id="game-over">
    <div id="over-text">游戏结束！</div>
    <div>得分：<span id="final-score">0</span></div>
    <button class="btn" id="again-btn">再来一局</button>
  </div>
</div>
<script>
// 粒子背景动画
const bgCanvas = document.getElementById('bg-canvas');
const bgCtx = bgCanvas.getContext('2d');
let particles = [];
function resizeBg() {
  bgCanvas.width = window.innerWidth;
  bgCanvas.height = window.innerHeight;
}
window.addEventListener('resize', resizeBg);
resizeBg();
function createParticles() {
  particles = [];
  for (let i = 0; i < 60; i++) {
    particles.push({
      x: Math.random() * bgCanvas.width,
      y: Math.random() * bgCanvas.height,
      r: Math.random() * 2 + 1,
      dx: (Math.random() - 0.5) * 0.7,
      dy: (Math.random() - 0.5) * 0.7,
      color: `hsl(${Math.random()*360}, 100%, 60%)`
    });
  }
}
createParticles();
function drawParticles() {
  bgCtx.clearRect(0, 0, bgCanvas.width, bgCanvas.height);
  for (let p of particles) {
    bgCtx.beginPath();
    bgCtx.arc(p.x, p.y, p.r, 0, Math.PI*2);
    bgCtx.fillStyle = p.color;
    bgCtx.shadowColor = p.color;
    bgCtx.shadowBlur = 12;
    bgCtx.fill();
    p.x += p.dx;
    p.y += p.dy;
    if (p.x < 0 || p.x > bgCanvas.width) p.dx *= -1;
    if (p.y < 0 || p.y > bgCanvas.height) p.dy *= -1;
  }
  // 连接线
  for (let i = 0; i < particles.length; i++) {
    for (let j = i+1; j < particles.length; j++) {
      let a = particles[i], b = particles[j];
      let dist = Math.hypot(a.x-b.x, a.y-b.y);
      if (dist < 80) {
        bgCtx.beginPath();
        bgCtx.moveTo(a.x, a.y);
        bgCtx.lineTo(b.x, b.y);
        bgCtx.strokeStyle = 'rgba(0,255,255,0.08)';
        bgCtx.lineWidth = 1;
        bgCtx.stroke();
      }
    }
  }
}
setInterval(drawParticles, 30);

// 游戏逻辑
const canvas = document.getElementById('game-canvas');
const ctx = canvas.getContext('2d');
const box = 24; // 单元格大小
const gridSize = canvas.width / box;
let snake, food, direction, nextDirection, score, highscore, speed, gameInterval, isGameOver;

function neonRect(x, y, w, h, color) {
  ctx.save();
  ctx.shadowColor = color;
  ctx.shadowBlur = 16;
  ctx.strokeStyle = color;
  ctx.lineWidth = 3;
  ctx.strokeRect(x, y, w, h);
  ctx.restore();
}
function neonCircle(x, y, r, color) {
  ctx.save();
  ctx.shadowColor = color;
  ctx.shadowBlur = 18;
  ctx.beginPath();
  ctx.arc(x, y, r, 0, Math.PI*2);
  ctx.fillStyle = color;
  ctx.fill();
  ctx.restore();
}
function drawSnake() {
  for (let i = 0; i < snake.length; i++) {
    let seg = snake[i];
    let color = i === 0 ? '#00ffe7' : `hsl(${180 + i*12}, 100%, 60%)`;
    // 主体填充
    ctx.save();
    ctx.fillStyle = color;
    ctx.globalAlpha = i === 0 ? 0.95 : 0.85;
    ctx.fillRect(seg.x*box+3, seg.y*box+3, box-6, box-6);
    ctx.restore();
    // 外描边
    ctx.save();
    ctx.lineWidth = 2.5;
    ctx.strokeStyle = i === 0 ? '#fff' : '#00ffe7';
    ctx.globalAlpha = 0.95;
    ctx.strokeRect(seg.x*box+3, seg.y*box+3, box-6, box-6);
    ctx.restore();
    // 蛇头高光
    if (i === 0) {
      ctx.save();
      ctx.beginPath();
      ctx.arc(seg.x*box+box/2, seg.y*box+box/2, box/5, 0, Math.PI*2);
      ctx.fillStyle = '#fff';
      ctx.globalAlpha = 0.18;
      ctx.fill();
      ctx.restore();
    }
  }
}
function drawFood() {
  // 食物主体
  ctx.save();
  ctx.beginPath();
  ctx.arc(food.x*box+box/2, food.y*box+box/2, box/2-5, 0, Math.PI*2);
  ctx.fillStyle = '#ff00e7';
  ctx.globalAlpha = 0.92;
  ctx.shadowColor = '#ff00e7';
  ctx.shadowBlur = 10;
  ctx.fill();
  ctx.restore();
  // 外描边
  ctx.save();
  ctx.beginPath();
  ctx.arc(food.x*box+box/2, food.y*box+box/2, box/2-5, 0, Math.PI*2);
  ctx.lineWidth = 2.5;
  ctx.strokeStyle = '#fff';
  ctx.globalAlpha = 0.85;
  ctx.stroke();
  ctx.restore();
  // 高光
  ctx.save();
  ctx.beginPath();
  ctx.arc(food.x*box+box/2-4, food.y*box+box/2-4, box/7, 0, Math.PI*2);
  ctx.fillStyle = '#fff';
  ctx.globalAlpha = 0.18;
  ctx.fill();
  ctx.restore();
}
function drawGrid() {
  ctx.save();
  ctx.strokeStyle = 'rgba(0,255,255,0.08)';
  ctx.lineWidth = 1;
  for (let i = 1; i < gridSize; i++) {
    ctx.beginPath();
    ctx.moveTo(i*box, 0);
    ctx.lineTo(i*box, canvas.height);
    ctx.stroke();
    ctx.beginPath();
    ctx.moveTo(0, i*box);
    ctx.lineTo(canvas.width, i*box);
    ctx.stroke();
  }
  ctx.restore();
}
function randomFood() {
  let pos;
  do {
    pos = {
      x: Math.floor(Math.random() * gridSize),
      y: Math.floor(Math.random() * gridSize)
    };
  } while (snake.some(seg => seg.x === pos.x && seg.y === pos.y));
  return pos;
}
function resetGame() {
  snake = [
    {x: 6, y: 10},
    {x: 5, y: 10},
    {x: 4, y: 10}
  ];
  direction = 'RIGHT';
  nextDirection = 'RIGHT';
  food = randomFood();
  score = 0;
  isGameOver = false;
  document.getElementById('score').textContent = score;
  document.getElementById('game-over').style.display = 'none';
  clearInterval(gameInterval);
  setGameSpeed(speed);
  draw();
}
function setGameSpeed(val) {
  speed = val;
  clearInterval(gameInterval);
  gameInterval = setInterval(gameLoop, 320 - speed*12);
}
function updateSpeedLabel(val) {
  let label = '中速';
  if (val <= 7) label = '慢速';
  else if (val >= 16) label = '快速';
  document.getElementById('speed-label').textContent = label;
}
function draw() {
  ctx.clearRect(0, 0, canvas.width, canvas.height);
  drawGrid();
  drawSnake();
  drawFood();
}
function gameLoop() {
  if (isGameOver) return;
  direction = nextDirection;
  let head = { ...snake[0] };
  if (direction === 'LEFT') head.x--;
  if (direction === 'RIGHT') head.x++;
  if (direction === 'UP') head.y--;
  if (direction === 'DOWN') head.y++;
  // 撞墙
  if (head.x < 0 || head.x >= gridSize || head.y < 0 || head.y >= gridSize) {
    return gameOver();
  }
  // 撞自己
  if (snake.some(seg => seg.x === head.x && seg.y === head.y)) {
    return gameOver();
  }
  snake.unshift(head);
  // 吃到食物
  if (head.x === food.x && head.y === food.y) {
    score++;
    document.getElementById('score').textContent = score;
    if (score > highscore) {
      highscore = score;
      localStorage.setItem('snake-highscore', highscore);
      document.getElementById('highscore').textContent = highscore;
    }
    food = randomFood();
  } else {
    snake.pop();
  }
  draw();
}
function gameOver() {
  isGameOver = true;
  clearInterval(gameInterval);
  document.getElementById('final-score').textContent = score;
  document.getElementById('game-over').style.display = 'block';
}
// 方向控制
window.addEventListener('keydown', e => {
  if (isGameOver) return;
  let key = e.key;
  if (key === 'ArrowLeft' || key === 'a' || key === 'A') {
    if (direction !== 'RIGHT') nextDirection = 'LEFT';
  } else if (key === 'ArrowUp' || key === 'w' || key === 'W') {
    if (direction !== 'DOWN') nextDirection = 'UP';
  } else if (key === 'ArrowRight' || key === 'd' || key === 'D') {
    if (direction !== 'LEFT') nextDirection = 'RIGHT';
  } else if (key === 'ArrowDown' || key === 's' || key === 'S') {
    if (direction !== 'UP') nextDirection = 'DOWN';
  }
});
// 速度调节
const speedSlider = document.getElementById('speed-slider');
speedSlider.addEventListener('input', e => {
  setGameSpeed(Number(e.target.value));
  updateSpeedLabel(Number(e.target.value));
});
// 重新开始
const restartBtn = document.getElementById('restart-btn');
const againBtn = document.getElementById('again-btn');
restartBtn.onclick = againBtn.onclick = resetGame;
// 初始化
window.onload = function() {
  highscore = Number(localStorage.getItem('snake-highscore')) || 0;
  document.getElementById('highscore').textContent = highscore;
  speed = Number(speedSlider.value);
  updateSpeedLabel(speed);
  resetGame();
};
</script>
</body>
</html> 